package com.zlll.winner.service.bbs;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.mapper.Wrapper;
import com.zlll.winner.business.model.bbs.BbsSubject;
import com.zlll.winner.business.model.bbs.BbsSubjectCity;
import com.zlll.winner.business.service.bbs.IBbsSubjectCityService;
import com.zlll.winner.business.vo.bbs.BbsSubjectVo;
import com.zlll.winner.enums.CommonEnum;
import com.zlll.winner.enums.bbs.SubjectEnum;
import com.zlll.winner.mapper.bbs.BbsSubjectCityMapper;
import com.zlll.winner.mapper.bbs.BbsSubjectMapper;
import com.zlll.winner.business.service.bbs.IBbsSubjectService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.apache.commons.lang3.StringUtils;
import org.apache.dubbo.config.annotation.Service;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.util.Assert;

import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;

/**
 * <p>
 * 论坛频道话题表 服务实现类
 * </p>
 *
 * @author Walert
 * @since 2019-09-12
 */
@Service
public class BbsSubjectServiceImpl extends ServiceImpl<BbsSubjectMapper, BbsSubject> implements IBbsSubjectService {

    @Autowired
    private IBbsSubjectCityService subjectCityService;

    @Resource
    private BbsSubjectCityMapper subjectCityMapper;

    /**
     * 论坛话题分页列表
     *
     * @param params
     * @return
     */
    @Override
    public Object fetchSubjectPage(JSONObject params) {
        Integer pageNo = params.getInteger("pageNo");
        Integer pageSize = params.getInteger("pageSize");

        IPage<BbsSubjectVo> page = new Page<>(pageNo, pageSize);
        QueryWrapper<BbsSubjectVo> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("t.is_del", CommonEnum.DelEnum.UNDEL.val());
        String subject = params.getString("subject");
        if(StringUtils.isNotBlank(subject)){
            queryWrapper.like("t.subject",subject);
        }
        Integer status = params.getInteger("status");
        if(status != null){
            if(status.equals(SubjectEnum.StatusEnum.WAIT.val())){
                queryWrapper.eq("t.status",SubjectEnum.StatusEnum.PUT_AWAY.val());
                Long curTime = System.currentTimeMillis();
                queryWrapper.gt("t.begin_time",curTime);
            }else{
                queryWrapper.eq("t.status",status);
            }
        }
        Long effectiveTime = params.getLong("effectiveTime");
        if(effectiveTime !=null){
            queryWrapper.ge("t.end_time",effectiveTime).le("t.begin_time",effectiveTime);
        }
        String cityCode = params.getString("cityCode");
        if(StringUtils.isNotBlank(cityCode)){
            queryWrapper.likeRight("m1.city_code",cityCode);
        }
        return baseMapper.selectPageByCustomer(page,queryWrapper);
    }

    /**
     * 保存话题表数据
     *
     * @param cityList
     * @param bbsSubject
     * @return
     */
    @Override
    public Object saveSubject(JSONArray cityList, BbsSubject bbsSubject) {
        List<BbsSubjectCity> bbsSubjectCities = cityList.toJavaList(BbsSubjectCity.class);
        bbsSubject.setPosts(0L);

        int result = baseMapper.insert(bbsSubject);
        if(result > 0 && bbsSubjectCities != null && bbsSubjectCities.size() > 0){
            bbsSubjectCities.stream().forEach(item->{
                item.setCreateTime(bbsSubject.getCreateTime());
                item.setCreateUser(bbsSubject.getCreateUser());
                item.setSubjectId(bbsSubject.getId());
            });
            subjectCityService.saveBatch(bbsSubjectCities);
        }
        return bbsSubject;
    }

    /**
     * 更新话题数据
     *
     * @param cityList
     * @param bbsSubject
     * @return
     */
    @Override
    public Object updateSubject(JSONArray cityList, BbsSubject bbsSubject) {
        List<BbsSubjectCity> bbsSubjectCities = cityList.toJavaList(BbsSubjectCity.class);
        baseMapper.updateById(bbsSubject);
        List<BbsSubjectCity> oldCityList = subjectCityService.list(
                Wrappers.<BbsSubjectCity>lambdaQuery()
                        .eq(BbsSubjectCity::getSubjectId, bbsSubject.getId())
        );
        List<BbsSubjectCity> saveOrUpdateList = new ArrayList<>();

        if(oldCityList!= null && oldCityList.size() > 0){
            Integer del = CommonEnum.DelEnum.DEL.val();
            Integer unDel = CommonEnum.DelEnum.UNDEL.val();
            Map<Long,BbsSubjectCity> oldMap = new HashMap<>(oldCityList.size());
            Set<Long> removeIdSet = new HashSet<>(oldCityList.size());
            for (BbsSubjectCity subjectCity : oldCityList) {
                oldMap.put(subjectCity.getCityId(),subjectCity);
                removeIdSet.add(subjectCity.getId());
            }
            for(BbsSubjectCity subjectCity : bbsSubjectCities){
                if(oldMap.containsKey(subjectCity.getCityId())){
                    BbsSubjectCity updateObj = oldMap.get(subjectCity.getCityId());
                    if(updateObj.getIsDel().equals(del));{
                        packingSubjectInfo(false,updateObj,bbsSubject);
                        updateObj.setIsDel(unDel);
                        saveOrUpdateList.add(updateObj);
                        removeIdSet.remove(updateObj.getId());
                    }
                }else{
                    packingSubjectInfo(true,subjectCity,bbsSubject);
                    saveOrUpdateList.add(subjectCity);
                }
            }
            if(removeIdSet.size() > 0){
                BbsSubjectCity updateObj = new BbsSubjectCity();
                packingSubjectInfo(false,updateObj,bbsSubject);
                updateObj.setIsDel(del);
                subjectCityService.update(updateObj,Wrappers.<BbsSubjectCity>lambdaQuery().in(BbsSubjectCity::getId,removeIdSet));
            }
        }else{
            if(bbsSubjectCities != null && bbsSubjectCities.size() > 0) {
                bbsSubjectCities.stream().forEach(item -> {
                    packingSubjectInfo(true,item,bbsSubject);
                    saveOrUpdateList.add(item);
                });
            }
        }
        if(saveOrUpdateList!= null && saveOrUpdateList.size() > 0){
            subjectCityService.saveOrUpdateBatch(saveOrUpdateList);
        }
        return bbsSubject;
    }

    /**
     * 根据position获取话题内容
     *
     * @param position
     * @return
     */
    @Override
    public Object getSubjectInfoByPosition(String position,String city) {
        long curTime = System.currentTimeMillis();
//        List<BbsSubjectCity> cityList = subjectCityMapper.selectList(Wrappers.<BbsSubjectCity>lambdaQuery().eq(BbsSubjectCity::getCityName, "广州市"));
//        Set<Long> subjectIds = cityList.stream().map(BbsSubjectCity::getSubjectId).collect(Collectors.toSet());

        QueryWrapper<BbsSubject> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("t.position",position);
        queryWrapper.eq("t.is_del",CommonEnum.DelEnum.UNDEL.val());
        queryWrapper.eq("t.status",SubjectEnum.StatusEnum.PUT_AWAY.val());
        queryWrapper.le("t.begin_time",curTime);
        queryWrapper.ge("t.end_time",curTime);
        queryWrapper.eq("m1.city_name",city);

        List<BbsSubject> bbsSubjects = baseMapper.getSubjectInfoByPositionAndCity(queryWrapper);
//        List<BbsSubject> bbsSubjects = baseMapper.selectList(
//                Wrappers.<BbsSubject>lambdaQuery()
//                        .eq(BbsSubject::getPosition, position)
//                        .eq(BbsSubject::getIsDel,CommonEnum.DelEnum.UNDEL.val())
//                        .eq(BbsSubject::getStatus, SubjectEnum.StatusEnum.PUT_AWAY.val())
//                        .le(BbsSubject::getBeginTime,curTime)
//                        .ge(BbsSubject::getEndTime,curTime)
//                        .orderByDesc(BbsSubject::getCreateTime));
        if(bbsSubjects != null && bbsSubjects.size() > 0){
            return bbsSubjects.get(0);
        }
        return null;
    }

    private void packingSubjectInfo(boolean isInsert,BbsSubjectCity subjectCity,BbsSubject bbsSubject){
        if(isInsert){
            subjectCity.setCreateTime(bbsSubject.getUpdateTime());
            subjectCity.setCreateUser(bbsSubject.getUpdateUser());
            subjectCity.setSubjectId(bbsSubject.getId());
        }else{
            subjectCity.setUpdateTime(bbsSubject.getUpdateTime());
            subjectCity.setUpdateUser(bbsSubject.getUpdateUser());
        }
    }
}
